﻿using System;

namespace Effects.Effects.Tools
{
    /// <summary>
    ///  Delay line with constant length.
    /// </summary>
    /// <remarks>
    ///  This class is the simplest delay line. It has constant length so every sample that is pushed in, is returned N samples later.
    /// </remarks>
    public class ConstantDelayLine : DelayLine
    {
        /// <summary>
        ///   Buffer for storing samples.
        /// </summary>
        protected double[] data;

        /// <summary>
        ///  Lenght of buffer in samples.
        /// </summary>
        protected int length;

        /// <summary>
        ///  Index to the data array
        /// </summary>
        private int index;

        /// <summary>
        ///  Creates ConstantDelayLine with given length
        /// </summary>
        /// <param name="length"> Length in samples </param>
        public ConstantDelayLine(int length)
        {
            this.length = length;
            this.index = 0;
            this.data = new double[length];
        }

        /// <summary>
        ///  Creates ConstantDelayLine with length that coresponds to the wanted delay time.
        /// </summary>
        /// <param name="time"> Delay time of each sample in miliseconds </param>
        /// <param name="sampleRate"> Sample rate of incoming samples </param>
        public ConstantDelayLine(double time, int sampleRate)
        {
            this.length = Convert.ToInt32(time * sampleRate / (double) 1000);
            this.index = 0;
            this.data = new double[length];
        }

        /// <summary>
        ///  Puts given sample into the delay line and returns delayed sample.
        /// </summary>
        /// <param name="sample"> Sample to put into the delay line. </param>
        /// <returns> Returns delayed sample </returns>
        public override double Step(double sample)
        {
            double ret = data[index];
            data[index] = sample;
            index--;
            if (index < 0)
                index += length;

            return data[index];
        }

        /// <summary>
        ///  Returns top of the delay line.
        /// </summary>
        public override double Top
        {
            get { return data[index]; }
        }
    }
}